package cn.hy.机考.part01;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.*;

/**
 * @author zhaomu
 *
 * 三、去重排序
 * 给定一个乱序的数组，删除所有的重复元素，使得每个元素只出现一次，并且按 照出现的次数从高到低进行排序， 相同出现次数按照第一次出现顺序进行先后排序。
 * 1 3 3 3 2 4 4 4 5
 * 3 4 1 2 5
 */
public class Demo03 {


    public static void main(String[] args) throws IOException {

        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        String[] params = br.readLine().trim().split(" ");
        int[] arr = new int[params.length];
        for (int i = 0; i < params.length; i++)
            arr[i] = Integer.parseInt(params[i]);
        int[] fx = fx(arr);

        for (int i = 0; i < fx.length; i++) {
            System.out.print(fx[i] + " ");
        }
        System.out.println();
        solve(arr);
    }


    public static void solve(int[] arr) {
//        Scanner in = new Scanner(System.in);
//        String[] str = in.nextLine().split(",");
//        int[] ints = new int[str.length];
//        for (int i = 0; i < ints.length; i++) {
//            ints[i] = Integer.parseInt(str[i]);
//        }
        LinkedHashMap<Integer, Integer> map = new LinkedHashMap<>();
        for (int i = 0; i < arr.length; i++) {  // 统计数字出现的频次
            map.put(arr[i], map.getOrDefault(arr[i], 0) + 1);
        }
        // Map按value排序，先将map转为list,再排序list
        LinkedList<Map.Entry<Integer,Integer>> list = new LinkedList<>(map.entrySet());
        list.sort((o1, o2) -> o2.getValue() - o1.getValue());
        for (int i = 0; i < list.size(); i++) {
            Map.Entry<Integer, Integer> entry = list.get(i);
            if (i != list.size() - 1) {
                System.out.print(entry.getKey() + ",");
            } else {
                System.out.println(entry.getKey());
            }
        }
    }


    public static int[] fx(int[] arr) {
        //收集节点信息
        HashMap<Integer, Node> map = new HashMap<>();
        int count = 0;
        for (int val : arr) {
            if (!map.containsKey(val)) {
                Node node = new Node(val, 1, count);
                map.put(val, node);
                count++;
            } else {
                Node node = map.get(val);
                node.count = node.count + 1;
                map.put(val, node);
            }
        }

        Collection<Node> values = map.values();
        Node[] nodes = values.toArray(new Node[0]);
        //生成信息后的原始节点信息
        for (Node n : nodes) {
            //System.out.println(n.val + "\t" + n.count + "\t" + n.order);
        }

        System.out.println();

        Arrays.sort(nodes, new NodeComparator());
        //排序后的节点
        for (Node node : nodes) {
            //System.out.println(node.val + "\t" + node.count + "\t" + node.order);
        }

        System.out.println();

        int[] res = new int[count];
        for (int i = 0; i < res.length; i++) {
            res[i] = nodes[i].val;
        }
        //System.out.println(Arrays.toString(res));

        return res;
    }


    private static class Node {
        public int val; //值
        public int count; //值重复次数
        public int order; //顺序

        public Node(int val, int count, int order) {
            this.val = val;
            this.count = count;
            this.order = order;
        }
    }

    private static class NodeComparator implements Comparator<Node> {
        @Override
        public int compare(Node o1, Node o2) {
            //构建比较器,统计次不同时按次数比较否则按出现顺序排序
            return o1.count != o2.count ? o2.count - o1.count : o1.order - o2.order;
        }
    }
}
